package com.lee.study.thrift.netty;

import io.netty.buffer.ByteBuf;
import io.netty.channel.ChannelHandlerContext;
import io.netty.channel.SimpleChannelInboundHandler;
import io.netty.util.CharsetUtil;
import org.apache.thrift.protocol.TMessage;
import org.apache.thrift.protocol.TMessageType;
import org.apache.thrift.protocol.TType;


public class ThriftDecoder extends SimpleChannelInboundHandler<ByteBuf> {

    protected static final int VERSION_MASK = 0xffff0000;
    protected static final int VERSION_1 = 0x80010000;

    @Override
    protected void channelRead0(ChannelHandlerContext ctx, ByteBuf msg) throws Exception {

//        readThrift(msg);
        response(ctx);

    }

    private void readThrift(ByteBuf msg) {
        if (msg.readableBytes() > 0) {
            //读出帧长度
            int frameSize = msg.readInt();
            System.out.println(frameSize);

//            byte[] buf = new byte[frameSize];
//            msg.readBytes(buf);
//            int off = 0;
//
//           int size = ((buf[off] & 0xff) << 24) |
//                            ((buf[off+1] & 0xff) << 16) |
//                            ((buf[off+2] & 0xff) <<  8) |
//                            ((buf[off+3] & 0xff));
//            System.out.println(size);

            int size = msg.getInt(msg.readerIndex());
            if (size < 0) {
                size = msg.readInt();
                int version = size & VERSION_MASK;
                if (version != VERSION_1) {
                    //抛出异常
                }
                //解析出TType
                byte type = (byte) (size & 0x000000ff);
                //解析出 name
                int nameLen = msg.readInt();
                ByteBuf nameByteBuf = msg.readBytes(nameLen);
                String name = nameByteBuf.toString(CharsetUtil.UTF_8);
                System.out.println();
                int seqId = msg.readInt();
                System.out.println(seqId);

                TMessage tMessage = new TMessage(name, type, seqId);
                System.out.println(tMessage);
            }
        }
    }

    private void response(ChannelHandlerContext ctx) {
        ByteBuf byteBuf = ctx.alloc().buffer();
        //写TMessage
        int version = VERSION_1 | TMessageType.REPLY;
        byteBuf.writeInt(version);
        byte[] nameBytes = "say".getBytes(CharsetUtil.UTF_8);
        byteBuf.writeInt(nameBytes.length);
        byteBuf.writeBytes(nameBytes);
        byteBuf.writeInt(1);
        //写返回值
        byteBuf.writeByte(TType.I32); //type
        byteBuf.writeShort(0); //id
        byteBuf.writeInt(888);
        byteBuf.writeByte(TType.STOP);

//        byte[] array = byteBuf.array();
//        int len = array.length;

        //int size = byteBuf.writerIndex();

//        ctx.write(size);
//        ctx.write(byteBuf);


        int len = byteBuf.readableBytes();
//        byte[] data = new byte[len];
//        byteBuf.getBytes(byteBuf.readerIndex(), data);


//        CompositeByteBuf response = ctx.alloc().compositeBuffer()
//                .addComponent(ctx.alloc().buffer().writeInt(len))
//                .addComponent(byteBuf);
        ctx.write(ctx.alloc().buffer().writeInt(len));
        ctx.write(byteBuf);
    }

    @Override
    public void channelReadComplete(ChannelHandlerContext ctx) throws Exception {
        ctx.flush();
    }
}
